package com.mr3chi.horoscopes;

import java.io.IOException;
import java.net.URL;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Locale;

import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.select.Elements;


public class NewsParser {
	
	public static final String HUFFINGTONPOST_NEWS 	= "div.horoFeature";
	public static final String HUFFINGTONPOST_TITLE = "div.horoFeature-hd";
	public static final String HUFFINGTONPOST_DESC 	= "div.horoFeature-content";
	public static final String HUFFINGTONPOST_DATE 	= "div.horoFeature-byline";
	public static final String HUFFINGTONPOST_LINK 	= "a[href]";
	
	private Document 		doc;
	private List<News> 		listCombinedNews;
	private List<WebPage> 	listWebPage;
	private WebPage 		pageHuffingtonPost;
	
	
	public NewsParser() {
		doc = null;
		
		listCombinedNews 	= new ArrayList<News>();
		listWebPage = new ArrayList<WebPage>();
		pageHuffingtonPost 	= new WebPage();
		pageHuffingtonPost.setPageId(WebPage.HUFFINGTONPOST);
		listWebPage.add(pageHuffingtonPost);
		
	}
	
	public void parseNext(int numberOfNews, List<String> needpage) throws IOException{
		
		int numberstillneed = numberOfNews;
		boolean allisout = false; //no more news on all pages (both stack and non-parsed ones yet)
		
		while(numberstillneed > 0 && !allisout){
			
			//search for the newest value
			Date maxValue = null;
			int maxPos = -1;
			
			allisout = true;
			
			for(int i = 0; i < listWebPage.size(); i++){
				
				//loading if there no news in the news-needed-stack
				if(listWebPage.get(i).isRead() &&
						listWebPage.get(i).isPageEnd() == false && 
						listWebPage.get(i).getPageList().size() == 0){
					if(needpage.contains(WebPage.HUFFINGTONPOST)){
						if(listWebPage.get(i).getPageId().equals(WebPage.HUFFINGTONPOST)){
							if(parseHuffingtonPostPage(listWebPage.get(i).getPageNum()+1)){
								allisout = false;
								if(listWebPage.get(i).getPageList().get(0).getDate() == null){
								}
								
								//MAX POS CHECK====================
								if(maxPos == -1){
									maxPos = i;
									maxValue = listWebPage.get(i).getPageList().get(0).getDate();
								}
								if(maxValue.before(listWebPage.get(i).getPageList().get(0).getDate())){
									maxValue = listWebPage.get(i).getPageList().get(0).getDate();
									maxPos = i;
								}
							}
						}
					}
					
					//more pages here...
				}else{
					allisout = false;
					
					//MAX POS CHECK====================
					if(maxPos == -1){
						maxPos = i;
						maxValue = listWebPage.get(i).getPageList().get(0).getDate();
					}
					if(maxValue.before(listWebPage.get(i).getPageList().get(0).getDate())){
						maxValue = listWebPage.get(i).getPageList().get(0).getDate();
						maxPos = i;
					}
				}
			}
			
			//got it
			if(maxPos != -1){
				listCombinedNews.add(listWebPage.get(maxPos).getPageList().get(0));
				listWebPage.get(maxPos).getPageList().remove(0);
				numberstillneed--;
			}	
		}
	}
	
	private boolean parseHuffingtonPostPage(int pageNumber) throws IOException {
		//get full url by combining all base url, suffix and page number
		String realUrl = WebPage.HUFFINGTONPOST + WebPage.HUFFINGTONPOST_SUFIX + pageNumber;
		
		//parse with jsoup
		doc = Jsoup.parse(new URL(realUrl).openStream(), "UTF-8", realUrl);
		
		//use selector
		Elements item = doc.select(HUFFINGTONPOST_NEWS);
		
		//set parsed page number to the webpage
		pageHuffingtonPost.setPageNum(pageNumber);
		
		//read and handle read value
		if(item.size() != 0){
			List<News> rs = readHuffingtonPost(item);
			if(rs != null && rs.size()!= 0){
				pageHuffingtonPost.getPageList().addAll(rs);
				return true;
			}
		}else{
			pageHuffingtonPost.setPageEnd(true);
		}
		return false;
	}
	
	private List<News> readHuffingtonPost(Elements elements){
		List<News> rs = new ArrayList<News>();
		
		for (int i=0; i<elements.size(); i++){
			String title ="";
			String image = "";
			String desc = "";
			String link = "";
			Date dateTime = null;
			
			Elements titleEles = elements.get(i).select(HUFFINGTONPOST_TITLE);
			if(titleEles.size()!=0){
				title = titleEles.get(0).text();
			}
			
			Elements descEles = elements.get(i).select(HUFFINGTONPOST_DESC);
			if(descEles.size()!=0){
				desc = descEles.get(0).text();
			}
			
			Elements linkEles = elements.get(i).select(HUFFINGTONPOST_LINK);
			if(linkEles.size()!=0){
				link = linkEles.get(0).attr("href");
			}
			
			Elements dateEles = elements.get(i).select(HUFFINGTONPOST_DATE);
			if(dateEles.size()!=0){
				try {
					dateTime = readHuffingtonDateTime(dateEles.get(0).text());
				} catch (ParseException e) {
					dateTime = new Date();
				}
			}
			
			rs.add(new News(title, image, desc, link, WebPage.HUFFINGTONPOST, dateTime));
		}
		
		return rs;
	}
	
	private Date readHuffingtonDateTime(String param) throws ParseException {
		String strdatetime;
		
		int atsymbolindex = param.indexOf("@");
		if(atsymbolindex>0){
			strdatetime = param.substring(15, atsymbolindex -1).trim()  + param.substring(atsymbolindex + 1);
			Date datetime = null;
			DateFormat sdf = new SimpleDateFormat("MMM d, yyyy hh:mm aa", Locale.US);
			datetime = sdf.parse(strdatetime);
			return datetime;
		}else{
			return null;
		}
	}
	
	public List<News> getCombinedNewsList(){
		return listCombinedNews;
	}
}
